//
// Created by 麻再挺 on 2021/12/8.
//

#include "queue.h"

Status Link_Queue_Init(LinkQueue *queue) {
    // 申请内存
    queue->front = queue->rear = malloc(sizeof(QNode));
    // 空间分配失败
    if (!queue->front) exit(OVERFLOW);
    // 设置队首的下一个节点为 NULL
    queue->front->next = NULL;
    return OK;
}

Status Link_Queue_Destroy(LinkQueue *queue) {
    while (queue->front) {
        // 设置队首的下一个节点为队尾
        queue->rear = queue->front->next;
        // 释放
        free(queue->front);
        // 设置队尾为队首
        queue->front = queue->rear;
    }
    return OK;
}

Status Link_Queue_Clear(LinkQueue *queue) {
    queue->front->next = NULL;
    queue->rear = queue->front;
    return OK;
}

Status Link_Queue_Empty(LinkQueue *queue) {
    return queue->front == queue->rear;
}

int Link_Queue_Length(LinkQueue *queue) {
    if (Link_Queue_Empty(queue)) return 0;
    // 计算方式: 使用队尾指针-队首指针所指向的数据
    return (int) (queue->rear - queue->front->next) + 1;
}

Status Link_Queue_GetHead(LinkQueue *queue, QElemType *elem) {
    if (Link_Queue_Empty(queue)) return ERROR;
    QNode *p = queue->front->next;
    *elem = p->data;
    return OK;
}

Status Link_Queue_Enter(LinkQueue *queue, QElemType elem) {
    // 申请空间
    QueueStr p = malloc(sizeof(QNode));
    // 分配失败
    if (!p) exit(OVERFLOW);
    // 赋值数据
    p->data = elem;
    // 设置下一节点为空
    p->next = NULL;
    // 设置队尾的下一个节点为 p
    queue->rear->next = p;
    // 设置队尾
    queue->rear = p;
    return OK;
}

Status Link_Queue_Deter(LinkQueue *queue, QElemType *elem) {
    // 空队列
    if (queue->front == queue->rear) return ERROR;
    // 获取队首
    QNode *p = queue->front->next;
    // 队首值
    *elem = p->data;
    // 移除队首元素
    queue->front->next = p->next;
    // 判断是否到队尾了
    if (queue->rear == p) queue->rear = queue->front;
    // 释放指针
    free(p);
    return OK;
}

void Link_Queue_Print(LinkQueue *queue) {
    // 获取队列长度
    int length = Link_Queue_Length(queue);
    // 获取初始节点
    QNode *elem = queue->front->next;
    for (int i = 0; i < length; ++i) {
        printf("%d", (elem+i)->data);
        if (i < length - 1) {
            printf(", ");
        }
    }
    printf("\n");
}
